﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.WebSockets;
using System.Net;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using BleSolution;

namespace YH.Bluetooth
{
    public class WebSocketServer
    {
        private const int Port = 8080;
        private static HttpListener _httpListener;
        private static CancellationTokenSource _cts;

        public static async Task StartAsync()
        {
            try
            {
                _cts = new CancellationTokenSource();
                _httpListener = new HttpListener();
                _httpListener.Prefixes.Add($"http://*:{Port}/");
                _httpListener.Start();
                Console.WriteLine("WebSocket 服务器启动，监听端口：" + Port);

                while (!_cts.Token.IsCancellationRequested)
                {
                    try
                    {
                        var context = await _httpListener.GetContextAsync().ConfigureAwait(false);
                        if (context.Request.IsWebSocketRequest)
                        {
                            _ = ProcessRequest(context); // Fire and forget but with proper error handling
                        }
                        else
                        {
                            context.Response.StatusCode = 400;
                            context.Response.Close();
                        }
                    }
                    catch (Exception ex)
                    {
                        LogHelper.WriteLog(ex);
                        Console.WriteLine($"HTTP Listener 错误：{ex}");
                    }
                }

                _httpListener.Stop();
                Console.WriteLine("WebSocket 服务器已停止。");
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(ex);
            }
          
        }

        public static void Stop()
        {
            try
            {
                _cts?.Cancel();
                _httpListener?.Stop();
                _cts?.Dispose();
                _httpListener?.Close();
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(ex);
            }
        }

        private static async Task ProcessRequest(HttpListenerContext context)
        {
            try
            {
                WebSocketContext wsContext;
                try
                {
                    wsContext = await context.AcceptWebSocketAsync(subProtocol: null).ConfigureAwait(false);
                }
                catch (Exception ex)
                {
                    LogHelper.WriteLog(ex);
                    context.Response.StatusCode = 500;
                    context.Response.Close();
                    Console.WriteLine($"无法建立 WebSocket 连接：{ex}");
                    return;
                }

                WebSocket webSocket = wsContext.WebSocket;
                byte[] buffer = new byte[1024 * 4]; // Increase buffer size to handle larger messages

                try
                {
                    while (webSocket.State == WebSocketState.Open && !_cts.Token.IsCancellationRequested)
                    {
                        var result = await webSocket.ReceiveAsync(new ArraySegment<byte>(buffer), _cts.Token).ConfigureAwait(false);
                        if (result.MessageType == WebSocketMessageType.Text)
                        {
                            string receivedMessage = Encoding.UTF8.GetString(buffer, 0, result.Count);
                            Console.WriteLine($"收到消息：{receivedMessage}");

                            // Echo the message back to the client
                            await webSocket.SendAsync(new ArraySegment<byte>(buffer, 0, result.Count), WebSocketMessageType.Text, result.EndOfMessage, _cts.Token).ConfigureAwait(false);
                        }
                        else if (result.MessageType == WebSocketMessageType.Close)
                        {
                            await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, string.Empty, _cts.Token).ConfigureAwait(false);
                            break;
                        }
                    }
                }
                catch (OperationCanceledException ex)
                {
                    Console.WriteLine("操作被取消。");
                    LogHelper.WriteLog(ex);
                }
                catch (Exception ex)
                {
                    Console.WriteLine($"WebSocket 连接异常：{ex}");
                    LogHelper.WriteLog(ex);
                    if (webSocket.State == WebSocketState.Open)
                    {
                        await webSocket.CloseAsync(WebSocketCloseStatus.InternalServerError, "内部服务器错误", _cts.Token).ConfigureAwait(false);
                    }
                }
                finally
                {
                    webSocket.Dispose();
                }
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(ex);
            }
        }
    }
}
